<?php

namespace app\system\controller;

use org\util\FileUtil;
use org\util\PhpExcelUtil;
use think\Db;
use think\Request;

class ImportController extends BaseController
{
    /**
     * 初始化
     * AreaController constructor.
     * @param Request $request
     */

    public function __construct(Request $request)
    {
        parent::__construct($request);
    }

    /**
     * 批量导入首页
     * @return mixed
     */
    public function index()
    {
        if ($this->request->isAjax()) {
            $data = $this->request->post();
            //处理属性特殊处理
            if (!empty($data['extend'])) {
                $data['col']['extend'] = implode(',', $data['extend']);
            }
            if (count(array_unique($data['col'])) == 1) { //选择有误
                $this->error('未选择对应关系！');
            } else {
                if ($data['col']['cid'] == -1) {
                    $this->error('请选择要导入的栏目');
                }
                $cache = cache('import_' . $this->getSiteId() . '_' . $data['channel']);
                foreach ($cache['fields'] as $v) {
                    if ($v['validate'] == '*') {
                        if ($data['col'][$v['field_name']] == -1) {
                            $this->error('请为' . $v['title'] . '字段选择导入项！');
                        }
                    }
                }
                //存入缓存对应关系
                $cache['import'] = $data;
                cache('import_' . $this->getSiteId() . '_' . $data['channel'], $cache, 3600); //缓存一小时
                $this->success('操作成功！', url('import', ['channel' => $data['channel']]));
            }
        }
        $moudle = cache('cms_moudle');
        $this->assign('moudle', $moudle);
        $this->assign('utype', $this->getUtype());
        return $this->fetch();
    }

    /**
     * 数据导入
     */
    public function import()
    {
        set_time_limit(0);
        ob_end_clean();
        header('Cache-Control: no-cache');
        header('X-Accel-Buffering: no');
        $channel = $this->request->param('channel');
        $cache   = cache('import_' . $this->getSiteId() . '_' . $channel);
        if (!$cache) {
            $this->error('数据丢失请重新上传');
        }
        //排除不导入的字段
        $col = [];
        foreach ($cache['import']['col'] as $index => $value) {
            if ($value >= 0) {
                $col[$index] = $value;
            }
        }
        $fields = array_column($cache['fields'], null, 'field_name');
        $acol   = array_intersect_key($fields, $col);
        if ($channel > 0) {
            $moudle     = cache('cms_moudle');
            $table      = $moudle[$cache['channel']]['table_name'];
            $defaultTpl = 'show_' . str_replace('cms_', '', $table);
        } elseif ($channel == -1) {
            $table      = 'shop_goods';
            $defaultTpl = 'shop_goods_show';
        } else {
            $this->error('模型不明确！');
        }
        $title = $cache['data'][0];
        unset($cache['data'][0]);
        $num = $faild = 0;
        $all = count($cache['data']);
        echo $this->fetch();
        ob_flush();
        flush();
        $errMsg = [];
        foreach ($cache['data'] as $index => $item) {
            $isInsert = true;
            foreach ($acol as $i => $v) {
                $value = $item[$col[$i]];
                //扩展属性字段特殊处理
                if ($i == 'extend') {
                    $extendItem = $col[$i];
                    if (!empty($extendItem)) {
                        $extendItem = explode(',', $extendItem);
                        $extendValues=[];
                        foreach ($extendItem as $it) {
                            $key            = str_replace(':', '：', $title[$it]);
                            $key            = str_replace(',', '，', $key);
                            $value          = str_replace(':', '：', $item[$it]);
                            $value          = str_replace(',', '，', $value);
                            $extendValues[] = $key . ':' . $value;
                        }
                        $value = implode(',', $extendValues);
                    }
                }
                switch ($v['field_type']) {
                    case 'string':
                        $value = htmlspecialchars($value);
                        break;
                    case 'number':
                        $value = (int)$value;
                        break;
                    case 'float':
                        $value = (float)$value;
                        break;
                }
                if ($v['validate'] == '*') { //必选处理
                    if ($value === '') {
                        $faildRow = $index+1;
                        $faild++;
                        $errMsg[] = "第{$faildRow}行数据不完整，原因：{$v['title']}为空或不合法！";
                        continue 2; //跳到最外层重新循环
                    }
                }
                if ($isInsert == true) {
                    $data[$v['table_name']][$i] = $value;
                }
            }
            //模板文件补全
            if (!array_key_exists('content_tpl', $data[$table])) {
                $data[$table]['content_tpl'] = $defaultTpl;
            }
            $data[$table]['cid']         = $cache['import']['col']['cid'];
            $data[$table]['uid']         = $this->getUid();
            $data[$table]['site_id']     = $this->getSiteId();
            $data[$table]['create_time'] = time();
            $data[$table]['update_time'] = time();
            if($channel>0){
                $data[$table]['mid']         = $cache['import']['channel'];
                $aid                         = Db::table($table)->insertGetId($data[$table]);
                //附表数据
                $data[$table . '_data']['aid'] = $aid;
                Db::table($table . '_data')->insert($data[$table . '_data']);
            }
            if($channel==-1){
                $goodsId = Db::table($table)->insertGetId($data[$table]);
                //附表数据
                $data[$table . '_data']['goods_id'] = $goodsId;
                Db::table($table . '_data')->insert($data[$table . '_data']);
                //sku表数据
                $data[$table . '_sku']['goods_id'] = $goodsId;
                Db::table($table . '_sku')->insert($data[$table . '_sku']);
            }
            $data=[]; //清空data
            $num++;
            $aria = ($num + $faild) / $all * 100;
            echo "<script>
                        $('#message').attr('style','width: $aria%');
                        $('#total').text($all);
                        $('#num').text($num);
                        $('#err').text($faild);
                        </script>";
            ob_flush();
            flush();
        }
        cache('import_' . $this->getSiteId() . '_' . $channel, null);
        $errHtml = '';
        if (!empty($errMsg)) {
            foreach ($errMsg as $e) {
                $errHtml .= "<p>{$e}</p>";
            }
        }
        echo "  <script>
                $('#mes').html('导入完成,共处理{$all}条数据，成功导入{$num}条，失败<a href=\"javascript:;\" onclick=\"showError();\">{$faild}</a>条。');
                $('#errHtml').html('{$errHtml}');
                </script>";
        ob_flush();
        flush();
    }

    /**
     * 格式化数据
     */
    public function formatData()
    {
        $channel  = $this->request->param('channel');
        $file     = $this->request->param('file');
        $file     = str_replace('/upload/', 'upload/', $file);
        $xlsData  = PhpExcelUtil::importExcel($file, 1);
        $xlsCount = count($xlsData);
        if ($xlsCount < 1) {
            $this->error('该文件没有数据！');
        }
        $this->allNum = $xlsCount - 1;
        //栏目缓存
        $html = '';
        if ($channel > 0) {
            $category = cache('cms_category' . $this->getSiteId());
            $html     = "<select name=\"col[cid]\" id=\"cid\" class=\"form-control\">";
            $html     .= "<option value='-1'>==选择栏目==</option>";
            foreach ($category as $cat) {
                //排除外部链接
                if ($cat['cat_type'] == 3) {
                    continue;
                }
                //非本模型栏目不显示
                if ($channel != $cat['mid']) {
                    continue;
                }
                if ($cat['cat_type'] == 1) { //频道页不允许添加内容
                    $disabled = ' disabled';
                } else {
                    $disabled = '';
                }
                $html .= "<option value='{$cat['cid']}' $disabled>{$cat['_name']}</option>";
            }
            $html .= "</select>";
        }
        if ($channel == -1) {
            $category = cache('goods_category' . $this->getSiteId());
            $html     = "<select name=\"col[cid]\" id=\"cid\" class=\"form-control\">";
            $html     .= "<option value='-1'>==选择栏目==</option>";
            foreach ($category as $cat) {
                //排除外部链接
                if ($cat['cat_type'] == 3) {
                    continue;
                }
                if ($cat['cat_type'] == 1) { //频道页不允许添加内容
                    $disabled = ' disabled';
                } else {
                    $disabled = '';
                }
                $html .= "<option value='{$cat['cid']}' $disabled>{$cat['_name']}</option>";
            }
            $html .= "</select>";
        }
        $isExtend = in_array($channel, [-1,1]) ? 1 : 0; //只有文章/商品模型导入扩展字段
        $data     = [
            'cid_select' => $html,
            'list'       => $xlsData[0],
            'channel'    => $channel,
            'total'      => $xlsCount - 1,
            'data'       => $xlsData,
            'fields'     => $this->getField($channel),
            'is_extend'  => $isExtend,
        ];
        cache('import_' . $this->getSiteId() . '_' . $channel, $data, 3600); //缓存一小时
        FileUtil::unlinkFile($file);
        unset($data['data']);
        $this->success('解析成功！', null, $data);
    }

    /**
     * 获取对应模型字段
     * @param $channel
     * @return array
     */
    private function getField($channel)
    {
        $fields = [];
        if ($channel > 0) {
            $cmsFields = cache('cms_field' . $channel);
            $fields    = [];
            foreach ($cmsFields as $k => $v) {
                if ($v['field_name'] != 'cid') { //排除栏目ID
                    $validate = '';
                    if (in_array($v['field_name'], ['title'])) {
                        $validate = '*';
                    }
                    $fields[] = [
                        'field_name' => $v['field_name'],
                        'title'      => $v['title'],
                        'field_type' => $v['i_field_type'],
                        'table_name' => $v['table_name'],
                        'validate'   => $validate,
                    ];
                }
            }
        }
        if ($channel == -1) {
            $fields = [
                ['field_name' => 'goods_name', 'title' => '商品标题', 'field_type' => 'string', 'table_name' => 'shop_goods', 'validate' => '*'],
                ['field_name' => 'sub_title', 'title' => '商品副标题', 'field_type' => 'string', 'table_name' => 'shop_goods', 'validate' => ''],
                ['field_name' => 'content_tpl', 'title' => '内容模板', 'field_type' => 'string', 'table_name' => 'shop_goods', 'validate' => ''],
                ['field_name' => 'goods_unit', 'title' => '商品单位', 'field_type' => 'string', 'table_name' => 'shop_goods', 'validate' => ''],
                ['field_name' => 'brand_id', 'title' => '商品品牌', 'field_type' => 'number', 'table_name' => 'shop_goods', 'validate' => ''],
                ['field_name' => 'album', 'title' => '商品缩略图', 'field_type' => 'string', 'table_name' => 'shop_goods', 'validate' => ''],
                ['field_name' => 'keywords', 'title' => '关键词', 'field_type' => 'string', 'table_name' => 'shop_goods', 'validate' => ''],
                ['field_name' => 'description', 'title' => '描述', 'field_type' => 'string', 'table_name' => 'shop_goods', 'validate' => ''],
                ['field_name' => 'is_on_sale', 'title' => '是否开放销售', 'field_type' => 'number', 'table_name' => 'shop_goods', 'validate' => ''],
                ['field_name' => 'is_best', 'title' => '精品', 'field_type' => 'number', 'table_name' => 'shop_goods', 'validate' => ''],
                ['field_name' => 'is_new', 'title' => '新品', 'field_type' => 'number', 'table_name' => 'shop_goods', 'validate' => ''],
                ['field_name' => 'is_hot', 'title' => '热销', 'field_type' => 'number', 'table_name' => 'shop_goods', 'validate' => ''],
                ['field_name' => 'is_commend', 'title' => '推荐', 'field_type' => 'number', 'table_name' => 'shop_goods', 'validate' => ''],
                ['field_name' => 'goods_sort', 'title' => '排序', 'field_type' => 'number', 'table_name' => 'shop_goods', 'validate' => ''],
                ['field_name' => 'alert_num', 'title' => '库存报警', 'field_type' => 'number', 'table_name' => 'shop_goods', 'validate' => ''],
                ['field_name' => 'content', 'title' => '商品内容', 'field_type' => 'string', 'table_name' => 'shop_goods_data', 'validate' => ''],
                ['field_name' => 'sku_sn', 'title' => '商品货号', 'field_type' => 'string', 'table_name' => 'shop_goods_sku', 'validate' => '*'],
                ['field_name' => 'market_price', 'title' => '市场价', 'field_type' => 'float', 'table_name' => 'shop_goods_sku', 'validate' => '*'],
                ['field_name' => 'goods_price', 'title' => '销售价', 'field_type' => 'string', 'table_name' => 'shop_goods_sku', 'validate' => '*'],
                ['field_name' => 'goods_stock', 'title' => '商品库存', 'field_type' => 'number', 'table_name' => 'shop_goods_sku', 'validate' => '*'],
                ['field_name' => 'goods_weight', 'title' => '商品重量', 'field_type' => 'number', 'table_name' => 'shop_goods_sku', 'validate' => '*'],
                ['field_name' => 'minimum', 'title' => '最小起订量', 'field_type' => 'number', 'table_name' => 'shop_goods_sku', 'validate' => '*'],
                ['field_name' => 'step', 'title' => '步长', 'field_type' => 'number', 'table_name' => 'shop_goods_sku', 'validate' => '*'],
                ['field_name' => 'extend', 'title' => '扩展属性', 'field_type' => 'string', 'table_name' => 'shop_goods_data', 'validate' => '']
            ];
        }
        return $fields;
    }

}